package com.jiangyg.mall.db;

import com.alibaba.druid.filter.Filter;
import com.alibaba.druid.pool.DruidDataSource;
import com.alibaba.druid.wall.WallConfig;
import com.jiangyg.mall.core.utils.Logger;
import com.jiangyg.mall.db.druid.SQLStatFilter;
import com.jiangyg.mall.db.druid.SQLWallFilter;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import org.springframework.transaction.annotation.EnableTransactionManagement;

import javax.sql.DataSource;
import java.util.ArrayList;
import java.util.List;

/**
 * 类描述：数据源配置
 */
@Slf4j
@Configuration
@EnableTransactionManagement
public class DataSourceAutoConfiguration implements InitializingBean {

    /**
     * 功能描述：构建数据源
     * <p>
     * <code>@Primary</code>标记着主库，作用就是在同类型存在多个bean的时候，选择标记的bean使用。<br>
     *
     * @return 返回数据源
     */
    @Primary
    @Bean(name = "dataSource", initMethod = "init")
    @ConfigurationProperties(prefix = "spring.connection", ignoreUnknownFields = false)
    public DataSource dataSource() {
        DruidDataSource dataSource = new DruidDataSource();
        // 配置代理过滤器
        List<Filter> filters = new ArrayList<>();
        filters.add(new SQLWallFilter(wallConfig()));
        filters.add(statFilter());
        dataSource.setProxyFilters(filters);
        return dataSource;
    }

    @Primary
    @Bean(name = "wallConfig")
    @ConfigurationProperties(prefix = "spring.druid.wall", ignoreUnknownFields = false)
    public WallConfig wallConfig() {
        return new WallConfig();
    }

    @Primary
    @Bean(name = "statFilter")
    @ConfigurationProperties(prefix = "spring.druid.stat", ignoreUnknownFields = false)
    public SQLStatFilter statFilter() {
        return new SQLStatFilter();
    }

    @Primary
    @Bean(name = "transactionManager")
    public DataSourceTransactionManager dataSourceTransactionManager(@Qualifier("dataSource") DataSource dataSource) {
        return new DataSourceTransactionManager(dataSource);
    }

    @Override
    public void afterPropertiesSet() {
        Logger.info(log, () -> "[项目启动]-初始化数据源配置……");
    }

}
